/*
This class is used to show list of products in system
 * 
 */

package com.memorytech.starchive;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;

import javax.xml.parsers.ParserConfigurationException;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;

import jp.co.memory_tech.starchive.R;

import org.xml.sax.InputSource;
import org.xml.sax.SAXException;
import org.xml.sax.XMLReader;

import android.app.Activity;
import android.content.SharedPreferences;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.BitmapFactory.Options;
import android.net.Uri;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.webkit.URLUtil;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.LinearLayout.LayoutParams;
import android.widget.ListView;
import android.widget.TextView;

import com.memorytech.starchive.entity.BarcodeInfo;
import com.memorytech.starchive.entity.FileInformation;
import com.memorytech.starchive.interfaceclass.OnListProductSelectedListener;
import com.memorytech.starchive.pulltorefresh.PullToRefreshListView;
import com.memorytech.starchive.pulltorefresh.PullToRefreshListView.OnRefreshListener;
import com.memorytech.starchive.utils.SaveData;
import com.memorytech.starchive.xmlparser.BarcodeParser;

// TODO: Auto-generated Javadoc
/**
 * The Class ListProduct.
 * 
 * @author Tam-LT
 */
public class ListProduct extends Fragment implements OnItemClickListener, OnRefreshListener {

    /** The m callback. */
    OnListProductSelectedListener mCallback;
    private PullToRefreshListView listView;
    private View view;
    private View footer;
    private ArrayList<FileInformation> arrayList;

    private BarcodeInfo barcodeInfo;

    public ArrayList<FileInformation> getArrayList() {
        return arrayList;
    }

    public void setArrayList(ArrayList<FileInformation> arrayList) {
        this.arrayList = arrayList;
    }

    /*
     * (non-Javadoc)
     * @see android.support.v4.app.Fragment#onCreate(android.os.Bundle)
     */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
    }

    /*
     * (non-Javadoc)
     * @see
     * android.support.v4.app.Fragment#onCreateView(android.view.LayoutInflater,
     * android.view.ViewGroup, android.os.Bundle)
     */
    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
            Bundle savedInstanceState) {
        view = inflater.inflate(R.layout.listproduct_pull, container, false);
        listView = (PullToRefreshListView) view.findViewById(R.id.pull_to_refresh_listview);
        arrayList = new ArrayList<FileInformation>();
        listView.setAdapter(new ListProductAdapter());
        listView.setOnItemClickListener(this);
        listView.setOnRefreshListener(this
                );
        footer = inflater.inflate(R.layout.footer, null);
        footer.setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                loadmore();

            }
        });
        // parseXml();
        return view;
    }

    /**
     * Loadmore.
     */
    public void loadmore() {
        // TODO Auto-generated method stub
        int temp = 0;
        int source = barcodeInfo.getFileInformations().size();
        // int lengt=0;
        listView.setSelection(arrayList.size() - 1);
        if (source - arrayList.size() > 5) {
            temp = 5;
        } else {
            temp = source - arrayList.size();
        }

        arrayList = new ArrayList<FileInformation>(barcodeInfo.getFileInformations()
                .subList(0, arrayList.size() + temp));
        resetFooter();

    }

    /**
     * Reset footer.
     */
    public void resetFooter() {
        // TODO Auto-generated method stub
        if (barcodeInfo.getFileInformations().size() > arrayList.size()) {
            showLoadMore();
        } else {
            hideLoadMore();
        }

    }

    /**
     * Show load more.
     */
    public void showLoadMore() {
        if (footer != null) {
            float density = getActivity().getResources().getDisplayMetrics().density;
            int marginTop = (int) (10 * density);
            int marginBottom = (int) (10 * density);
            LinearLayout.LayoutParams layout = new LinearLayout.LayoutParams(
                    LayoutParams.FILL_PARENT, LayoutParams.WRAP_CONTENT);
            layout.bottomMargin = marginBottom;
            layout.topMargin = marginTop;
            footer.findViewById(R.id.footer_msg).setLayoutParams(layout);
            // footer.setVisibility(View.VISIBLE);
            if (listView.getFooterViewsCount() == 0) {
                listView.addFooterView(footer);
            }
        }
    }

    /**
     * Hide load more.
     */
    public void hideLoadMore() {
        if (footer != null) {
            // footer.setVisibility(View.GONE);
            listView.removeFooterView(footer);
        }

    }

    /*
     * (non-Javadoc)
     * @see android.support.v4.app.Fragment#onStart()
     */
    @Override
    public void onStart() {
        super.onStart();

        // When in two-pane layout, set the listview to highlight the selected
        // list item
        // (We do this during onStart because at the point the listview is
        // available.)
        if (getFragmentManager().findFragmentById(R.id.detail_fragment) != null) {
            listView.setChoiceMode(ListView.CHOICE_MODE_SINGLE);
        }
    }

    /*
     * (non-Javadoc)
     * @see android.support.v4.app.Fragment#onAttach(android.app.Activity)
     */
    @Override
    public void onAttach(Activity activity) {
        super.onAttach(activity);

        // This makes sure that the container activity has implemented
        // the callback interface. If not, it throws an exception.
        try {
            mCallback = (OnListProductSelectedListener) activity;
        } catch (ClassCastException e) {
            throw new ClassCastException(activity.toString()
                    + " must implement OnHeadlineSelectedListener");
        }
    }

    /**
     * Parses the xml.
     */
    private void parseXml() {
        // TODO Auto-generated method stub

        try {
            SAXParserFactory spf = SAXParserFactory.newInstance();
            SAXParser sp = spf.newSAXParser();

            XMLReader xr = sp.getXMLReader();

            BarcodeParser dataHandler = new BarcodeParser();
            xr.setContentHandler(dataHandler);
            // InputStream inputStream =
            // getActivity().getAssets().open("sample.xml");
            // xr.parse(new InputSource(inputStream));

            String hostname = SaveData.getInstance(getActivity()).gethostname();
            Log.i("Tamle", "hostname is: " + hostname);

            if (hostname.length() > 0) {
                String request_url = String.format(
                        "http://%s/StarchiveWebInterface/index.php/GetInformation", hostname);
                Log.i("Tamle", "request url is: " + request_url);
                xr.parse(new InputSource(
                        new FileInputStream(
                                getDataSource(request_url))));
                barcodeInfo = dataHandler.getData();
                // barcodeInfo = dataHandler.getData();
            }

        } catch (ParserConfigurationException pce) {
            Log.e("SAX XML", "sax parse error", pce);
            barcodeInfo = null;
        } catch (SAXException se) {
            Log.e("SAX XML", "sax error", se);
            barcodeInfo = null;
        } catch (IOException ioe) {
            Log.e("SAX XML", "sax parse io error", ioe);
            barcodeInfo = null;
        }
        resetListData();

    }

    /**
     * The Class ListProductAdapter. It's used to display product item on list
     * view
     */
    public class ListProductAdapter extends BaseAdapter {

        /*
         * (non-Javadoc)
         * @see android.widget.Adapter#getCount()
         */
        @Override
        public int getCount() {
            // TODO Auto-generated method stub
            if (arrayList != null) {
                return arrayList.size();
            } else {
                return 0;
            }
        }

        /*
         * (non-Javadoc)
         * @see android.widget.Adapter#getItem(int)
         */
        @Override
        public Object getItem(int position) {
            // TODO Auto-generated method stub
            return null;
        }

        /*
         * (non-Javadoc)
         * @see android.widget.Adapter#getItemId(int)
         */
        @Override
        public long getItemId(int position) {
            // TODO Auto-generated method stub
            return 0;
        }

        /*
         * (non-Javadoc)
         * @see android.widget.Adapter#getView(int, android.view.View,
         * android.view.ViewGroup)
         */
        @Override
        public View getView(int position, View convertView, ViewGroup parent) {
            // TODO Auto-generated method stub
            View v;
            if (convertView == null) {

                LayoutInflater li = getActivity().getLayoutInflater();
                v = li.inflate(R.layout.product_item, null);
            } else {
                v = convertView;
            }
            FileInformation productItem = arrayList.get(position);
            TextView fileName = (TextView) v
                    .findViewById(R.id.filename);
            fileName.setText(productItem.getName());
            TextView date = (TextView) v
                    .findViewById(R.id.date);
            date.setText(productItem.getCreateTime());
            TextView tapeNo = (TextView) v
                    .findViewById(R.id.tapeno);
            tapeNo.setText("" + barcodeInfo.getTape());

            ImageView imageView = (ImageView) v.findViewById(R.id.status_image);
            if (productItem.getFileStatus().equalsIgnoreCase("Online")) {
                imageView.setImageResource(R.drawable.starchive_green);
            } else if (productItem.getFileStatus().equalsIgnoreCase("Offline")) {
                imageView.setImageResource(R.drawable.starchive_red);
            } else {
                imageView.setImageResource(R.drawable.starchive_yellow);
            }

            return v;
        }

    }

    /**
     * Gets the data source.
     * 
     * @param path the path
     * @return the data source
     * @throws IOException Signals that an I/O exception has occurred.
     */
    private String getDataSource(String path) throws IOException {
        if (!URLUtil.isNetworkUrl(path)) {
            return path;
        } else {
            URL url = new URL(path);
            URLConnection cn = url.openConnection();
            cn.connect();
            InputStream stream = cn.getInputStream();
            if (stream == null)
                throw new RuntimeException("stream is null");
            File temp = File.createTempFile("mediaplayertmp", ".dat");
            temp.deleteOnExit();
            String tempPath = temp.getAbsolutePath();
            FileOutputStream out = new FileOutputStream(temp);
            byte buf[] = new byte[128];
            do {
                int numread = stream.read(buf);
                if (numread <= 0)
                    break;
                out.write(buf, 0, numread);
                Log.i("TamLe", "write sample.xml to sdcard");
            } while (true);
            try {
                stream.close();
            } catch (IOException ex) {
                Log.e("Tamle", "error: " + ex.getMessage(), ex);
            }
            return tempPath;
        }
    }

    /*
     * (non-Javadoc)
     * @see
     * android.widget.AdapterView.OnItemClickListener#onItemClick(android.widget
     * .AdapterView, android.view.View, int, long)
     */
    @Override
    public void onItemClick(AdapterView<?> arg0, View arg1, int arg2, long arg3) {
        // TODO Auto-generated method stub
        if (listView.isRefreshing()) {
            return;
        }
        if (arg2 <= 0) {
            return;
        }
        // Notify the parent activity of selected item
        FileInformation fileInformation = barcodeInfo.getFileInformations().get(arg2 - 1);
        fileInformation.setTapeNo(barcodeInfo.getTape());
        mCallback.onListProductSelected(fileInformation);
        // // Set the item as checked to be highlighted when in two-pane layout
        listView.setItemChecked(arg2 - 1, true);

    }

    /*
     * (non-Javadoc)
     * @see eu.erikw.PullToRefreshListView.OnRefreshListener#onRefresh()
     */
    @Override
    public void onRefresh() {
        // TODO Auto-generated method stub
        Log.i("Tamle", "Pull to refresh");

        listView.postDelayed(new Runnable() {
            @Override
            public void run() {
                Log.i("Tamle", "Pull to refresh completed");
                resetListData();
                listView.onRefreshComplete();
            }
        }, 2000);

    }

    /**
     * Reset list data.
     */
    public void resetListData() {
        if (barcodeInfo != null && barcodeInfo.getFileInformations() != null) {
            if (barcodeInfo.getFileInformations().size() > 5) {
                arrayList = new ArrayList<FileInformation>(barcodeInfo
                        .getFileInformations().subList(0, 5));
                showLoadMore();
            } else {
                arrayList = new ArrayList<FileInformation>(
                        barcodeInfo.getFileInformations());
                hideLoadMore();
            }
        } else {
            arrayList = new ArrayList<FileInformation>();
            hideLoadMore();
        }

    }

    public void updateData() {
        // TODO Auto-generated method stub
        parseXml();
    }

}
